Skip to content

bugfix(physics): Prevent dead units from repeatedly dealing crash damage on collision with non-buildings#2204

Merged
xezon merged 5 commits into
TheSuperHackers:mainfrom
Stubbjax:fix-dead-unit-crash-damage
May 20, 2026
Merged

bugfix(physics): Prevent dead units from repeatedly dealing crash damage on collision with non-buildings#2204
xezon merged 5 commits into
TheSuperHackers:mainfrom
Stubbjax:fix-dead-unit-crash-damage

Conversation

@Stubbjax
Copy link
Copy Markdown

@Stubbjax Stubbjax commented Jan 28, 2026

Closes #2015

This change fixes an issue where dead vehicles repeatedly trigger VehicleCrashesIntoNonBuildingWeapon when colliding with mines, causing continuous damage to nearby units and structures.

This weapon is hardcoded into the physics update, and is fired when a vehicle falls onto a non-building object - the intent being that a vehicle deals some 'crush' damage to a victim it lands on. It is especially problematic in the case of mines as the mines cannot destroy the already-dead vehicle. The issue is most apparent with Technicals due to their frequent involvement in bombing runs and their tendency to fling themselves forwards upon death.

The fix makes the weapon only deal damage to the collided target.

There is also a building-specific crash block that fires VehicleCrashesIntoBuildingWeapon when a vehicle crashes into a building, however this results in the immediate destruction of the crashing vehicle, and so is not as problematic.

Before

The Propaganda Center dies due to dead Technicals firing VehicleCrashesIntoNonBuildingWeapon every frame

YES_DAMAGE.mp4

After

The Propaganda Center survives unscathed as VehicleCrashesIntoNonBuildingWeapon only targets the mines

NO_DAMAGE.mp4

@Stubbjax Stubbjax self-assigned this Jan 28, 2026
@Stubbjax Stubbjax added Bug Something is not working right, typically is user facing Minor Severity: Minor < Major < Critical < Blocker Gen Relates to Generals ZH Relates to Zero Hour NoRetail This fix or change is not applicable with Retail game compatibility labels Jan 28, 2026
@greptile-apps
Copy link
Copy Markdown

greptile-apps Bot commented Jan 28, 2026

Greptile Summary

This PR fixes a bug where dead vehicles (notably Technicals after bombing runs) would fire VehicleCrashesIntoNonBuildingWeapon every physics frame on collision with objects like mines, causing continuous AoE damage to nearby units and structures. The fix replaces the original createAndFireTempWeapon (which fires an AoE blast centered on the crashing vehicle) with a direct attemptDamage call targeting only the colliding object (other).

  • The new path is guarded by #if RETAIL_COMPATIBLE_CRC, so the original AoE behavior is preserved when building in CRC-compatible mode for replay parity with retail.
  • DamageInfo is correctly populated (type, death type, source ID, source player mask, and primary damage with a neutral WeaponBonus), matching the fields set by the standard dealDamageInternal path for a direct-hit victim.
  • The fire FX is preserved via an explicit FXList::doFXObj call. The concern about missing m_sourcePlayerMask raised in previous review threads is addressed in this PR.

Confidence Score: 5/5

Safe to merge. The change is narrowly scoped to the non-building crash damage path, the original retail behavior is fully preserved under the CRC guard, and the direct damage call populates all required DamageInfo fields correctly.

The fix correctly replaces an AoE weapon blast at the crashing vehicle position with a single targeted attemptDamage call on the colliding object. All fields written by the standard dealDamageInternal path for a direct-hit victim are present, including m_sourcePlayerMask which was the concern from prior review threads. The WeaponBonus default gives base damage with no bonuses, which is appropriate for a physics-driven crash event.

No files require special attention.

Important Files Changed

Filename Overview
Generals/Code/GameEngine/Source/GameLogic/Object/Update/PhysicsUpdate.cpp Replaces AoE crash weapon fire with a targeted direct damage call on the colliding object, with m_sourcePlayerMask properly populated; gated behind #if RETAIL_COMPATIBLE_CRC to preserve original behavior for CRC builds.
GeneralsMD/Code/GameEngine/Source/GameLogic/Object/Update/PhysicsUpdate.cpp Identical fix applied to the Zero Hour version of PhysicsUpdate.cpp; no differences in logic relative to the Generals copy.

Reviews (6): Last reviewed commit: "tweak: Assign source player mask" | Re-trigger Greptile

@Mauller
Copy link
Copy Markdown

Mauller commented Jan 28, 2026

This doesn't properly resolve #2015, the issue with aircraft landing on mines is that the aircraftSlowDeathBehaviour module for the chinook is waiting to see when the unit hits the ground. But it never does and remains floating over the mines above the ground detection threshold.

The issue is that the mines block the slow death code from detecting when the chinook hits the ground properly and prevents the carcus from ever clearing itself.

@Stubbjax
Copy link
Copy Markdown
Author

This doesn't properly resolve #2015, the issue with aircraft landing on mines is that the aircraftSlowDeathBehaviour module for the chinook is waiting to see when the unit hits the ground. But it never does and remains floating over the mines above the ground detection threshold.

The issue is that the mines block the slow death code from detecting when the chinook hits the ground properly and prevents the carcus from ever clearing itself.

That sounds like a separate issue? This fix targets the issue as described; "GLA Technical kills/damages building when dying by China Mines".

@Mauller
Copy link
Copy Markdown

Mauller commented Jan 28, 2026

This doesn't properly resolve #2015, the issue with aircraft landing on mines is that the aircraftSlowDeathBehaviour module for the chinook is waiting to see when the unit hits the ground. But it never does and remains floating over the mines above the ground detection threshold.
The issue is that the mines block the slow death code from detecting when the chinook hits the ground properly and prevents the carcus from ever clearing itself.

That sounds like a separate issue? This fix targets the issue as described; "GLA Technical kills/damages building when dying by China Mines".

Ah yeah, i glanced over it and read the bit about migs and chinooks in the issue as well.

The other week Fish and i were looking into the same issue but with aircraft and it is a problem with the death behaviour modules.

I don't think your change here will fix their behaviour since they are never properly set to being effectively dead since they remain stuck in their death crash handling.

@Stubbjax
Copy link
Copy Markdown
Author

I don't think your change here will fix their behaviour since they are never properly set to being effectively dead since they remain stuck in their death crash handling.

Is effectively dead not exactly the status that should apply here? As far as I'm aware that status is applied as soon as health becomes depleted.

@Mauller
Copy link
Copy Markdown

Mauller commented Feb 3, 2026

I don't think your change here will fix their behaviour since they are never properly set to being effectively dead since they remain stuck in their death crash handling.

Is effectively dead not exactly the status that should apply here? As far as I'm aware that status is applied as soon as health becomes depleted.

I would need to check again, have you seen if this also prevents falling planes and helicopters applying continuous damage when they land on mines?

Or checked if falling planes and helicopters apply any damage when landing on things?

@Stubbjax
Copy link
Copy Markdown
Author

Stubbjax commented Feb 3, 2026

I would need to check again, have you seen if this also prevents falling planes and helicopters applying continuous damage when they land on mines?

This will affect anything that would have previously repeatedly applied VehicleCrashesIntoNonBuildingWeapon on collision with mines. This should include aircraft as they all have the necessary VEHICLE KindOf, but I have not explicitly tested it.

if (obj->isKindOf(KINDOF_VEHICLE))
#else
// TheSuperHackers @bugfix Stubbjax 28/01/2026 Prevent dead units from repeatedly dealing damage.
if (obj->isKindOf(KINDOF_VEHICLE) && !obj->isEffectivelyDead())
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suspect this fix is not correct. I put a breakpoint into this branch and on the very first hit the Object is already dead, which means that this weapon now never fires once.

Image

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you clarify what you mean? You have described the fix as intended, which is to prevent crash damage from triggering if the object is effectively dead.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok how do we know the intent is to not apply damage once when dead technical crashes?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We do not. We can only say the new intent is to not have it deal any damage in order to improve gameplay.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I expect that a dead vehicle crashing into something can apply damage once. For example if a plane is shot and its rubble hits the ground, then it applies collision damage once. Otherwise only alive vehicles would cause crash damage, which may not be intuitive for players. This is also more in line with what the original code did (incorrectly).

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I suggest add 1 new bit flag to PhysicsBehavior, default it to 1, check if it is 1 before one of the createAndFireTempWeapon, and then set it to 0 afterwards.

This way, this physics weapon can only ever fire once.

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When should it be reset to 1?

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Check if there is a way to determine if a collision event is "new". I suspect PhysicsBehavior::onCollide keeps being called every frame because the object is not pushed away from the collider, but keeps intersecting while flying through it.

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm still struggling to understand why such behaviour is desirable. Currently, if a dead unit falls on a non-building obstacle (e.g. rocks, mines, shipping containers, etc.), then it deals crush damage in a radius while in contact. Even if we reduce this to a single damage instance per obstacle, the behaviour is still effectively arbitrary and can yield confusing and unexpected results.

THE_ROCKS.mp4

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So instead perhaps disable the crash damages entirely?

@Piddox
Copy link
Copy Markdown

Piddox commented Apr 6, 2026

This seems to have hit a stall. I would like to showcase how badly this bug impacts competitive gameplay in GO currently, by showing some clips I've saved over the last weeks:

Marakar vs TumStep in ZH League, prize pool $280:
WF dying to its own mines

MiKwArY vs BoYcaH^, same tournament ZH League:
 stupid unfair bugs

Kill toll vs Raging_K, sponsored challenge by Yamen (they ended up replaying this game due to the bug):
mines bug

Same set, next game:
mines bug

And some ffg examples:
Massacre vs Logica:

2026-04-17.14-20-22.mp4

Rudwan vs Logica (instant ragequit):

2026-04-06.11-30-40.mp4

Memphis vs Rusty:

2026-04-06.11-29-39.mp4

Mamo in 3v3 50k TW:

2026-04-04.21-59-26.mp4

I could go on, this is just a fraction of the times I've seen it happening. Honestly, it's a plague infesting GO competitive gameplay, and since players don't know any better, it's bad for the reputation of both GO and TSH.

It appears we have a fix ready to be deployed here. It's just not completely clear whether the collision damage should not be applied at all (which this fix does), or whether the intended behavior of the EA devs was to have collision damage to occur once.

Would it be possible to continue that debate in a new issue, whilst merging this one to main, as a temporary fix, so that the players at least can enjoy this bug fix and not be confronted by this heavily game-impacting bug behavior?

@xezon
Copy link
Copy Markdown

xezon commented Apr 18, 2026

Needs a decision. Current fix does not appear to be satisfying.

@Stubbjax
Copy link
Copy Markdown
Author

Needs a decision. Current fix does not appear to be satisfying.

I think the ideal solution would be to forgo the isEffectivelyDead check and instead apply damage directly to the collided object(s) rather than spawning a weapon template.

So instead of:

TheWeaponStore->createAndFireTempWeapon(getPhysicsBehaviorModuleData()->m_vehicleCrashesIntoNonBuildingWeaponTemplate, obj, obj->getPosition());

We would have:

const WeaponTemplate* weaponTemplate = getPhysicsBehaviorModuleData()->m_vehicleCrashesIntoNonBuildingWeaponTemplate;

DamageInfo damageInfo;
damageInfo.in.m_damageType = weaponTemplate->getDamageType();
damageInfo.in.m_deathType = weaponTemplate->getDeathType();
damageInfo.in.m_sourceID = obj->getID();
damageInfo.in.m_amount = weaponTemplate->m_primaryDamage;

other->attemptDamage(&damageInfo);

This would mean only rocks or mines or whatever other prop objects would receive the damage directly, while nearby units and buildings remain unaffected. We could think about doing this for the building crash too, to avoid the inconsistent damage application entirely. We can then look at implementing dedicated death weapons for crashed aircraft further down the track.

Thoughts?

@xezon
Copy link
Copy Markdown

xezon commented Apr 19, 2026

Can crashed units collide with multiple units or just ever one?

@Stubbjax
Copy link
Copy Markdown
Author

Can crashed units collide with multiple units or just ever one?

Well it wouldn't be units, but yes, I imagine any applicable obstacles within the geometry bounds would run through onCollide.

@xezon
Copy link
Copy Markdown

xezon commented Apr 19, 2026

It appears logical to only apply damage to directly collided things. It just needs to make sure to not re-apply the damage on every repeated collision event.

@Stubbjax
Copy link
Copy Markdown
Author

It appears logical to only apply damage to directly collided things. It just needs to make sure to not re-apply the damage on every repeated collision event.

Does it matter if it does? We don't know what object(s) might be in the way. If we only apply e.g. 30 damage once to a 100-HP object, then the object will remain and potentially block the dead object.

@xezon
Copy link
Copy Markdown

xezon commented Apr 19, 2026

But isn't the repeated damage exactly the problem here? A dead vehicle falling onto a building will not be pushed off the building. It will continueosly collide and spam damage events every logic frame.

@Stubbjax
Copy link
Copy Markdown
Author

But isn't the repeated damage exactly the problem here? A dead vehicle falling onto a building will not be pushed off the building. It will continueosly collide and spam damage events every logic frame.

If the object collides with a building, the object is destroyed. The problem occurs when the object collides with non-building obstacles and spawns damage instances during those collisions which affect other nearby objects.

@xezon
Copy link
Copy Markdown

xezon commented Apr 19, 2026

Ok. You can make a POC for this and then we see how that looks.

@Stubbjax
Copy link
Copy Markdown
Author

Ok. You can make a POC for this and then we see how that looks.

Pushed an update. This essentially yields the same benefits as the original fix, with the added bonus that falling dead objects don't get stuck above destructible non-building obstacles.

Before

Colliding with an obstacle deals damage to nearby objects

LIX_CRASH_BEFORE.mp4

After

Colliding with an obstacle only deals damage to collided objects

LIX_CRASH_AFTER.mp4

@xezon xezon added Major Severity: Minor < Major < Critical < Blocker and removed Minor Severity: Minor < Major < Critical < Blocker labels Apr 20, 2026
Copy link
Copy Markdown

@xezon xezon left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you also prepare a change for the crash damage on buildings?

Comment thread Generals/Code/GameEngine/Source/GameLogic/Object/Update/PhysicsUpdate.cpp Outdated
@Stubbjax
Copy link
Copy Markdown
Author

Can you also prepare a change for the crash damage on buildings?

As part of this change or separately?

@xezon
Copy link
Copy Markdown

xezon commented Apr 30, 2026

As part of this change or separately?

Can be separate if it requires seperate description.

@Piddox
Copy link
Copy Markdown

Piddox commented May 9, 2026

I see green ticks everywhere. Is there anything else needed for this to be merged into main?

@xezon
Copy link
Copy Markdown

xezon commented May 9, 2026

I was waiting for the partner fix to merge them together

@Stubbjax Stubbjax force-pushed the fix-dead-unit-crash-damage branch from 4e17363 to fd6d974 Compare May 17, 2026 12:17
@Stubbjax Stubbjax force-pushed the fix-dead-unit-crash-damage branch from fd6d974 to f970d13 Compare May 20, 2026 05:50
@greptile-apps
Copy link
Copy Markdown

greptile-apps Bot commented May 20, 2026

Want your agent to iterate on Greptile's feedback? Try greploops.

@xezon xezon changed the title bugfix: Prevent dead units from repeatedly dealing crash damage on collision with non-buildings bugfix(physics): Prevent dead units from repeatedly dealing crash damage on collision with non-buildings May 20, 2026
@xezon xezon merged commit 1594474 into TheSuperHackers:main May 20, 2026
17 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Bug Something is not working right, typically is user facing Gen Relates to Generals Major Severity: Minor < Major < Critical < Blocker NoRetail This fix or change is not applicable with Retail game compatibility ZH Relates to Zero Hour

Projects

None yet

Development

Successfully merging this pull request may close these issues.

GLA Technical kills/damages building when dying by China Mines

4 participants